/**
 * This file is Copyright © 2008 Software Craftsmen Limited. All Rights Reserved.
 */
package com.softwarecraftsmen.orogeny.filing.absolutePathMetaData;

import com.softwarecraftsmen.orogeny.filing.absolutePathMetaData.posixIdentifiers.PosixGroupIdentifier;
import com.softwarecraftsmen.orogeny.filing.absolutePathMetaData.posixIdentifiers.PosixUserIdentifier;
import static com.softwarecraftsmen.orogeny.filing.absolutePathMetaData.posixPermissions.FixedReadOnlyPosixClassPermissions.*;
import com.softwarecraftsmen.orogeny.filing.absolutePathMetaData.posixPermissions.PosixClassPermissions;
import org.jetbrains.annotations.NotNull;

import static java.lang.String.format;
import static java.util.Locale.UK;

public class FixedReadOnlyAbsolutePathMetaData implements AbsolutePathMetaData
{
	private final long sizeInBytes;
	private final long modificationTimeInMillisecondsSince1970;
	private final PosixUserIdentifier owner;
	private final PosixClassPermissions ownerPermissions;
	private final PosixGroupIdentifier group;
	private final PosixClassPermissions groupPermissions;
	private final PosixClassPermissions othersPermissions;

	public FixedReadOnlyAbsolutePathMetaData(final long sizeInBytes, final long modificationTimeInMillisecondsSince1970, final @NotNull PosixUserIdentifier owner, final @NotNull PosixClassPermissions ownerPermissions, final @NotNull PosixGroupIdentifier group, final @NotNull PosixClassPermissions groupPermissions, final @NotNull PosixClassPermissions othersPermissions)
	{
		if (sizeInBytes < 0)
		{
			throw new IllegalArgumentException(format(UK, "sizeInBytes can not be negative. It is %1$s", sizeInBytes));
		}
		this.sizeInBytes = sizeInBytes;
		this.modificationTimeInMillisecondsSince1970 = modificationTimeInMillisecondsSince1970;
		if (modificationTimeInMillisecondsSince1970 < 0)
		{
			throw new IllegalArgumentException(format(UK, "modificationTimeInMillisecondsSince1970 can not be negative. It is %1$s", modificationTimeInMillisecondsSince1970));
		}
		this.owner = owner;
		this.ownerPermissions = ownerPermissions;
		this.group = group;
		this.groupPermissions = groupPermissions;
		this.othersPermissions = othersPermissions;
	}

	@NotNull
	public static FixedReadOnlyAbsolutePathMetaData typicalDataFilePermissions(final long sizeInBytes, final long modificationTimeInMillisecondsSince1970, final @NotNull PosixUserIdentifier owner, final @NotNull PosixGroupIdentifier group)
	{
		return new FixedReadOnlyAbsolutePathMetaData(sizeInBytes, modificationTimeInMillisecondsSince1970, owner, ReadWrite, group, Read, Read);
	}

	@NotNull
	public static FixedReadOnlyAbsolutePathMetaData typicalDirectoryPermissions(final long modificationTimeInMillisecondsSince1970, final @NotNull PosixUserIdentifier owner, final @NotNull PosixGroupIdentifier group)
	{
		return new FixedReadOnlyAbsolutePathMetaData(0, modificationTimeInMillisecondsSince1970, owner, ReadWriteExecute, group, ReadCanSearchInDirectory, ReadCanSearchInDirectory);
	}

	@NotNull
	public static FixedReadOnlyAbsolutePathMetaData typicalSymbolicLinkPermissions(final long modificationTimeInMillisecondsSince1970, final @NotNull PosixUserIdentifier owner, final @NotNull PosixGroupIdentifier group)
	{
		return new FixedReadOnlyAbsolutePathMetaData(0, modificationTimeInMillisecondsSince1970, owner, ReadWriteExecute, group, ReadWriteExecute, ReadWriteExecute);
	}

	public long sizeInBytes()
	{
		return sizeInBytes;
	}

	public long modificationTimeInMillisecondsSince1970()
	{
		return modificationTimeInMillisecondsSince1970;
	}

	@NotNull
	public PosixUserIdentifier owner()
	{
		return owner;
	}

	@NotNull
	public PosixClassPermissions ownerPermissions()
	{
		return ownerPermissions;
	}

	@NotNull
	public PosixGroupIdentifier group()
	{
		return group;
	}

	@NotNull
	public PosixClassPermissions groupPermissions()
	{
		return groupPermissions;
	}

	@NotNull
	public PosixClassPermissions othersPermissions()
	{
		return othersPermissions;
	}
}
